<?php
namespace App\Common\Lib\Hyperf\Amqp;

use App\Common as com;
use App\Common\Lib\Hyperf\Amqp\ConnectionFactory as thisConnectionFactory;
use Hyperf\Contract\ConfigInterface;
use Psr\Container\ContainerInterface;
use Hyperf\Amqp\AMQPConnection;
use Hyperf\Amqp\Params;
use Hyperf\Utils\Arr;
use InvalidArgumentException;
use Hyperf\Amqp\IO\SwooleIO;
use Hyperf\Contract\StdoutLoggerInterface;

class ConnectionFactory extends com\Lib\LibBase {


	/**
	 * @var ContainerInterface
	 */
	protected $container;

	/**
	 * @var ConfigInterface
	 */
	protected $config;

	/**
	 * @var AMQPConnection[][]
	 */
	protected $connections = [];

	public function __construct() {
		$this->container = com\Lib\Hyperf\Container::getContainer();
		$this->config = $this->container->get( ConfigInterface::class );
		//
		parent::__construct();
	}


	public function makeOfPool( string $pool ):AMQPConnection	{
		$config = $this->getConfig( $pool );
		//
		$host = $config['host'] ?? 'localhost';
		$port = $config['port'] ?? 5672;
		$user = $config['user'] ?? 'guest';
		$password = $config['password'] ?? 'guest';
		$vhost = $config['vhost'] ?? '/';
		$openSSL = $config['open_ssl'] ?? false;

		$params = new Params( Arr::get( $config, 'params', [] ) );
		$io = new SwooleIO(
			$host,
			$port,
			$params->getConnectionTimeout(),
			$params->getReadWriteTimeout(),
			$openSSL,
		);
		//
		$connection = new AMQPConnection(
			$user,
			$password,
			$vhost,
			$params->isInsist(),
			$params->getLoginMethod(),
			null,
			$params->getLocale(),
			$io,
			$params->getHeartbeat(),
			$params->getConnectionTimeout(),
			$params->getChannelRpcTimeout()
		);
		//
		return $connection->setParams($params)
			->setLogger($this->container->get(StdoutLoggerInterface::class));
	}

	protected function getConfig( string $pool ):array {
		$key = sprintf( 'amqp.%s', $pool );
		if ( ! $this->config->has( $key ) ) {
			throw new InvalidArgumentException( sprintf( 'config[%s] is not exist!', $key ) );
		}
		return $this->config->get( $key );
	}

	// ===============================
	//
	//
	// 下面为静态方法
	//
	//
	// ===============================

	/**
	 * @return $this
	 */
	public static function makeOfNew():self {
	    return self::make();
	}

}
